# -*- coding : utf-8 -*-
from django.shortcuts import render,get_object_or_404
from django.http import HttpResponse,StreamingHttpResponse,JsonResponse
from django.conf import settings
from .models import File, myTask
from .tasks import looploop
from celery.task.control import revoke
import subprocess
import os
import sys
import zipfile
import re
import sys
import time
from upload.Testimg import Testimage

flag=0
hlist=[]

def getAppBaseInfo(apkpath,res):
    #检查版本号等信息
    aaptinfo = subprocess.Popen("/opt/software/sdks/android/sdk/build-tools/25.0.2/aapt d badging %s" % apkpath, shell=True, stdout=subprocess.PIPE)
    output = aaptinfo.stdout.read() 
    output = bytes.decode(output)
    #print (output)
    match = re.compile("package: name='(\S+)' versionCode='(\d+)' versionName='(\S+)' platformBuildVersionName='\S+'").match(output)
    if not match:
        raise Exception("can't get packageinfo")

    packagename = match.group(1)
    versionCode = match.group(2)
    versionName = match.group(3)
    with open(res, 'w', encoding='utf-8') as f:
        f.write("Apk Package's Name:" + packagename + "\n" + "The Version of Code:" + versionCode + "\n" + "The Version of Apk:" + versionName + "\n")

        outList = output.split('\n')
        for line in outList:
            if line.startswith('uses-permission:'):
                f.write(line.split('=')[1] + "\n")
    #f.close()
    #def getCurrentDirApk():
    #    for dir in os.walk(os.curdir):
    #        for filename in dir[2]:
    #            if os.path.splitext(filename)[1] == '.apk':
    #                print('find apk:', filename)
    #                return filename
    #def insertFile(apkName, f):
    #    output = os.popen("/opt/software/sdks/android/sdk/build-tools/25.0.2/aapt a %s %s" % (apkName, f)).read()

#if __name__ == "__main__":
    #获得apk名
    #if len(sys.argv) == 1:
    #    apkName = getCurrentDirApk()
    #else:
    #    apkName = sys.argv[1]
    #if not apkName:
    #    print('can not find apk!!!')
    #    exit()
    #getAppBaseInfo(apkName)
    #向apk中插入文件
    #insertfile = 'insertfile.txt'
    #f = open(insertfile, "w+")

def uploadfile(request):
    
    if request.method == "GET":
        return render(request,'upload.html')
    else:
        try:
            fileName = request.FILES['picture']
        except KeyError:
            return JsonResponse({'task_id':'null','test_time':time.strftime("%Y-%m-%d %H:%M:%S", time.localtime()),'apk_name':'null'})
        url = os.path.join(settings.MEDIA_ROOT,'images', fileName.name)
        read=open(url,'wb+')
        for chunk in fileName.chunks():
            read.write(chunk)
        read.close()
        #Upload Successfully
        str1=fileName.name
        res_url = os.path.join(settings.MEDIA_ROOT,'result',str1.split(".")[0]+'_res.txt')
        #f=open(res_url,'wb+')
        
        #获取上传的apk的基本信息，输出到指定文件夹以供下载
        #res=os.popen('python3.6 ./images/Testapk2.py ./images/'+ fileName.name + ' > ./result/' + str1.split(".")[0]+'_res.txt')
        dist = {}
        # dist['status'] = "Test Successfully!"
        # try:
        #     getAppBaseInfo(url,res_url)
        # except Exception :
        #     dist['status'] = 'Info Test Error!(Maybe this apk cannot be analyzed)'    
        #try:

        global flag
        global hlist

        # flag,hlist = Testimage(str1)
        try:
            task = looploop.delay(str1)
            start_time = time.strftime("%Y-%m-%d %H:%M:%S", time.localtime())
            task_id = task.id
            q = myTask(task_id=task_id,
                       apk_name=str1,
                       detect_time=start_time)
            q.save()
            return JsonResponse({'task_id':task_id,'test_time':start_time,'apk_name':str1})
        except Exception as e:
            return JsonResponse({'task_id':str(e),'test_time':time.strftime("%Y-%m-%d %H:%M:%S", time.localtime()),'apk_name':str1})
        # if flag == 1:
        #     dist['is_harmful'] = flag
        # else:
        #     dist['is_harmful'] = flag
        # #except Exception :
        # #    dist['status'] = 'Images Test Error!'

        # #cmd='python3.6 ./images/Testapk2.py ./images/'+ fileName.name
        # #cmd=cmd.split(" ")
        # #Apkinfo=subprocess.Popen(cmd,shell=False,stdout=subprocess.PIPE)
        # #byte_content=Apkinfo.stdout.read()
        # #Apkinfo
        # #str_content=byte_content.decode('gbk')
        # #f.write(str_content)
        # #f.close()
        # dist['test_time'] = time.strftime("%Y-%m-%d %H:%M:%S", time.localtime())
        # dist['apk_name'] = str1
        # dist['res_link'] = res_url
        # dist['res_file'] = str1.split(".")[0]+'_res.txt'
	
        # return render(request,'upload.html',dist)
#models.File.objects.update_or_create(file=fileName)

def task_status(request,task_id):
    global detectResult
    cur_task = looploop.AsyncResult(task_id)
    if cur_task.state == 'PROGRESS':
        res = {'state':'progress','progress':cur_task.info.get('i',0),'result':''}
    elif cur_task.state == 'SUCCESS':
        res = {'state':'success','progress':100,'result':cur_task.get()}
        detectResult = cur_task.get()
        harm_msg_num = detectResult[0]
        harm_msg_list = detectResult[1]
        total_msg_num = detectResult[2]
        harm_msg_url = detectResult[3]
        #try:
        q = myTask.objects.get(task_id=task_id)
        q.harmful_msg_num = harm_msg_num
        q.total_msg_num = total_msg_num
        q.report_url = harm_msg_url
        # dont forget to save
        q.save()
        #except myTask.DoesNotExist:
        #    res = {'state':'waitting','progress':0,'result':''}
    elif cur_task.state == 'PENDING':
        res = {'state':'waitting','progress':0,'result':''}
    else:
        res = {'state':cur_task.state,'progress':cur_task.info.get('i',0),'result':''}
    return JsonResponse(res)

def stop_task(request,task_id):
    # cur_task = looploop.AsyncResult(task_id)
    try:
        revoke(task_id,terminate=True)
        return JsonResponse({'result':'success'})
    except Exception as e:
        return JsonResponse({'result':str(e)})


def genreport(request,task_id):
    # dist = {}
    # if detectResult[0] >= 1: 
    #     dist['flag'] = detectResult[0]
    #     dist['list'] = detectResult[1]
    # else: 
    #     dist['flag'] = 0
    #     dist['list'] = []
    q = get_object_or_404(myTask,task_id=task_id)
    harm_msg_num = q.harmful_msg_num
    total_msg_num = q.total_msg_num 
    harm_msg_url = q.report_url
    apk_name = q.apk_name
    test_time = q.detect_time
    dist = {}
    dist['total'] = total_msg_num
    dist['harm'] = harm_msg_num
    dist['harm_list'] = []
    with open(harm_msg_url,"r") as f:
        for eachline in f:
            eachline = eachline.strip('\n')
            dist['harm_list'].append(eachline)
    dist['apk_name'] = apk_name
    dist['test_time'] = test_time
    return render(request,'report.html',dist)

def downloadfile(request,data):


    def file_itertor(file_name,chunk_size=512):
        with open(file_name) as f:
            while True:
                c=f.read(chunk_size)
                if c:
                    yield c
                else:
                    break
    file_name=os.path.join(settings.MEDIA_ROOT,'result',data)
    download_file= data
    response=StreamingHttpResponse(file_itertor(file_name))
    response['Content-Type'] = 'application/octet-stream'
    response['Content-Disposition'] = 'attachment;filename="{0}"'.format(download_file)
    return response
